package com.quectel.cms.controller.sys;


import cn.hutool.core.lang.func.LambdaUtil;
import cn.hutool.core.util.DesensitizedUtil;
import cn.hutool.crypto.digest.BCrypt;
import com.quectel.cms.constants.CmsRedisCacheConstants;
import com.quectel.cms.controller.BaseController;
import com.quectel.cms.util.SessionHolder;
import com.quectel.constant.global.SystemConstants;
import com.quectel.constant.global.annotation.RequirePermissions;
import com.quectel.sys.module.sys.dto.SysUserDto;
import com.quectel.sys.module.sys.service.SysGroupService;
import com.quectel.sys.module.sys.service.SysUserService;
import com.quectel.util.common.Page;
import com.quectel.util.common.RandomUtils;
import com.quectel.util.common.Request;
import com.quectel.util.common.Response;
import com.quectel.util.redis.RedisUtils;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.tags.Tag;
import org.apache.commons.lang3.StringUtils;
import org.apache.dubbo.config.annotation.DubboReference;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;

import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Objects;

/**
 * @author caolu
 * @email louis.cao@quectel.com
 * @date 2019-04-01 13:06:24
 */
@RestController
@RequestMapping("sysUser")
@Tag(name = "SysUserController", description = "系统用户相关api")
public class SysUserController extends BaseController {

    @DubboReference
    private SysUserService sysUserService;
    @DubboReference
    private SysGroupService sysGroupService;

    /**
     * 列表
     */
    @GetMapping("list")
    @RequirePermissions(values = "sysUser:list")
    @Operation(summary = "系统用户列表分页查询列表")
    public Response<Page<SysUserDto>> list(@RequestParam Map<String, Object> params) {
        //查询列表数据
        Request request = Request.configParams(params).like("mobile");
        super.fillAuthorityData(params);

        List<SysUserDto> list = sysUserService.queryList(params);
        int total = sysUserService.queryTotal(params);
        if (list != null) {
            for (SysUserDto sysUserDto : list) {
                sysUserDto.setIsFrozen((byte) 0);
                if (sysUserDto.getGroupId() != null) {
                    sysUserDto.setSysGroup(sysGroupService.selectById(sysUserDto.getGroupId()));
                }
                String isFrozen = RedisUtils.get(CmsRedisCacheConstants.WRONG_COUNT + sysUserDto.getId());
                if (StringUtils.isNotBlank(isFrozen)) {
                    sysUserDto.setIsFrozen((byte) 1);
                }

                // 脱敏
                sysUserDto.setUsername(DesensitizedUtil.chineseName(sysUserDto.getUsername()));
                sysUserDto.setMobile(DesensitizedUtil.mobilePhone(sysUserDto.getMobile()));
                sysUserDto.setEmail(DesensitizedUtil.email(sysUserDto.getEmail()));
            }
        }

        Page<SysUserDto> page = new Page(request.getPageNo(), request.getPageSize(), total, list);

        return Response.<Page<SysUserDto>>ok().wrap(page);
    }


    /**
     * 根据id查询系统用户记录
     */
    @GetMapping("info/{id}")
    @RequirePermissions(values = "sysUser:info")
    @Operation(summary = "根据id查询系统用户记录")
    public Response<SysUserDto> info(@PathVariable("id") Long id) {
        //查询权限
        Map<String, Object> params = new HashMap<>();
        params.put(LambdaUtil.getFieldName(SysUserDto::getId), id);
        super.fillAuthorityData(params);
        int num = sysUserService.queryTotal(params);
        if (num <= 0) {
            return Response.error(SystemConstants.ILLEGAL_MSG);
        }
        SysUserDto sysUserDto = sysUserService.selectById(id);

        return Response.<SysUserDto>ok().wrap(sysUserDto);
    }

    /**
     * 保存系统用户记录
     */
    @PostMapping("save")
    @RequirePermissions(values = "sysUser:edit")
    @Operation(summary = "保存系统用户记录")
    public Response<Object> save(@RequestBody @Validated SysUserDto sysUserDto) {
        SysUserDto dbUser = sysUserService.selectByAccount(sysUserDto.getAccount());
        if (dbUser != null) {
            return Response.error("该账号已存在");
        }
        super.fillSaveCommonData(sysUserDto);

        String randomPassword = RandomUtils.genStrongPassword(6, 8);
        sysUserDto.setPassword(BCrypt.hashpw(randomPassword, BCrypt.gensalt()));

        sysUserService.save(sysUserDto);
        return Response.ok().wrap(randomPassword);
    }

    /**
     * 修改
     */
    @PostMapping("update")
    @RequirePermissions(values = "sysUser:edit")
    @Operation(summary = "修改系统用户记录")
    public Response<Object> update(@RequestBody @Validated SysUserDto sysUserDto) {
        Map<String, Object> params = new HashMap<>();
        params.put(LambdaUtil.getFieldName(SysUserDto::getId), sysUserDto.getId());
        super.fillAuthorityData(params);
        int num = sysUserService.queryTotal(params);
        if (num <= 0) {
            return Response.error(SystemConstants.ILLEGAL_MSG);
        }

        SysUserDto dbUser = sysUserService.selectByAccount(sysUserDto.getAccount());
        if (dbUser != null && !Objects.equals(sysUserDto.getId(), dbUser.getId())) {
            return Response.error("您修改的账号已存在");
        }
        if (dbUser != null && SystemConstants.YES.equals(dbUser.getIsTenantAdmin())) {
            if (!Objects.equals(dbUser.getGroupId(), sysUserDto.getGroupId())) {
                // 如果是超级组的管理员不允许修改
                return Response.error("系统的默认用户无法变更用户组");
            }
        }
        super.fillEditCommonData(sysUserDto);
        sysUserService.updateById(sysUserDto);
        return Response.ok();
    }

    /**
     * 修改
     */
    @PostMapping("resetPwd")
    @RequirePermissions(values = "sysUser:reset")
    @Operation(summary = "重置系统用户密码")
    public Response<Object> resetPwd(@RequestBody Long[] ids) {

        for (Long id : ids) {
            Map<String, Object> params = new HashMap<>();
            params.put(LambdaUtil.getFieldName(SysUserDto::getId), id);

            int num = sysUserService.queryTotal(params);
            if (num <= 0) {
                return Response.error(SystemConstants.ILLEGAL_MSG);
            }
            String randomPassword = RandomUtils.genStrongPassword(6, 8);
            sysUserService.updatePassword(id, BCrypt.hashpw(randomPassword, BCrypt.gensalt()));
            return Response.ok().wrap(randomPassword);
        }
        return Response.ok();
    }

    /**
     * 删除
     */
    @PostMapping("delete")
    @RequirePermissions(values = "sysUser:del")
    @Operation(summary = "删除系统用户记录")
    public Response<Object> delete(@RequestBody Long[] ids) {
        for (Long id : ids) {

            Map<String, Object> params = new HashMap<>();
            params.put(LambdaUtil.getFieldName(SysUserDto::getId), id);
            super.fillAuthorityData(params);
            int num = sysUserService.queryTotal(params);
            if (num <= 0) {
                return Response.error(SystemConstants.ILLEGAL_MSG);
            }

            SysUserDto sysUserDto = sysUserService.selectById(id);
            if ("admin".equalsIgnoreCase(sysUserDto.getAccount())) {
                return Response.error("超级管理员不能被删除");
            }
            //需要踢出已经授权的token
            SessionHolder.removeUserToken(id);

        }
        sysUserService.deleteBatch(ids);
        return Response.ok();
    }

    /**
     * 解冻账号
     */
    @PostMapping("unfreeze")
    @RequirePermissions(values = "sysUser:unfreeze")
    @Operation(summary = "批量解冻用户账号")
    public Response<Object> unfreeze(@RequestBody Long[] ids) {
        for (Long id : ids) {
            Map<String, Object> params = new HashMap<>();
            params.put(LambdaUtil.getFieldName(SysUserDto::getId), id);
            super.fillAuthorityData(params);
            int num = sysUserService.queryTotal(params);
            if (num <= 0) {
                return Response.error(SystemConstants.ILLEGAL_MSG);
            }
            RedisUtils.del(CmsRedisCacheConstants.WRONG_COUNT + id);
        }
        return Response.ok();
    }


    /**
     * 启用或者禁用
     */
    @PostMapping("enableOrDisable")
    @RequirePermissions(values = "sysUser:enableOrDisable")
    @Operation(summary = "启用或者禁用用户账号")
    public Response<Object> enableOrDisable(@RequestBody Long[] ids) {
        for (Long id : ids) {
            //查询权限
            Map<String, Object> params = new HashMap<>();
            params.put(LambdaUtil.getFieldName(SysUserDto::getId), id);
            super.fillAuthorityData(params);
            int num = sysUserService.queryTotal(params);
            if (num <= 0) {
                return Response.error(SystemConstants.ILLEGAL_MSG);
            }
            SysUserDto sysUserDto = sysUserService.selectById(id);
            if (SystemConstants.NORMAL.equals(sysUserDto.getStatus())) {
                //状态正常的更新为禁用
                SysUserDto updateObj = new SysUserDto();
                updateObj.setId(sysUserDto.getId());
                updateObj.setStatus(SystemConstants.ABNORMAL);
                fillEditCommonData(updateObj);
                sysUserService.updateByIdWithoutRelation(updateObj);
                //需要踢出已经授权的token
                SessionHolder.removeUserToken(id);
            } else {
                //状态禁用的的更新为正常
                SysUserDto updateObj = new SysUserDto();
                updateObj.setId(sysUserDto.getId());
                updateObj.setStatus(SystemConstants.NORMAL);
                fillEditCommonData(updateObj);
                sysUserService.updateByIdWithoutRelation(updateObj);
            }
        }
        return Response.ok();
    }


}
